Subclasses and Inheritance

Description

In Designing an Xbasic Class we offhandedly asked "Do we need 14 subclasses, one for each different database API?" and answered "It's one way to go." Let's explain what subclasses are, and why are they useful. Subclasses are classes derived from a base class. In Xbasic, that is done with the INHERITS keyword:

DEFINE CLASS MySubClass INHERITS MyBaseClass

Subclasses inherit the capabilities of the base class, which they can use, modify, add to, or override. A subclass can be differentiated from its base class by

  • adding member variables (properties)

  • adding member functions (methods)

  • redefining (overriding) member functions inherited from the base class

Subclasses can themselves become the base classes for other classes. In our stored procedure example, we discovered that some databases use the CALL keyword to invoke a stored procedure, while other databases use the EXEC keyword to invoke a stored procedure. We could define a class hierarchy that reflects this:

DEFINE CLASS StoredProc
...
END CLASS
 
DEFINE CLASS ExecSP INHERITS StoredProc
DIM  m_SP_Keyword as C = "EXEC"
...
END CLASS
 
DEFINE CLASS CallSP INHERITS StoredProc
DIM  m_SP_Keyword as C = "CALL"
...
END CLASS
 
DEFINE CLASS SQLServer_SP INHERITS ExecSP
...
END CLASS
 
DEFINE CLASS Sybase_SP INHERITS ExecSP
...
END CLASS
 
DEFINE CLASS MySQL_SP INHERITS CallSP
...
END CLASS
 
DEFINE CLASS Oracle_SP INHERITS CallSP
...
END CLASS
 
DEFINE CLASS DB2_SP INHERITS CallSP
...
END CLASS
 
...

Then the functionality common to all databases would be implemented in StoredProc, the functionality common to all databases that use the EXEC keyword would be implemented in ExecSP, the functionality common to all databases that use the CALL keyword would be implemented in CallSP, and the datatabase-specific functionality would be implemented in SQLServer_SP, MySQL_SP, and so on.

Is-a and Has-a relationships

If we think about our current example, we can say accurately that SQL Server is a database. In object-oriented design terms, this "is a" relationship is appropriate for inheritance. Let's think about a different area. A Ford F150 truck is a type of motor vehicle. So an F150 class can inherit from a Truck class, which can inherit from a MotorVehicle class. All well and good. On the other hand, a motor vehicle has a driver, but is not a kind of driver. So instead of inheritance, we would use a different mechanism to express the relationship: the MotorVehicle class would have a member variable which is an instance of the Driver class.

DEFINE CLASS Driver
...
END CLASS
 
DEFINE CLASS MotorVehicle
...
DIM m_driver AS Driver
...
END CLASS

Before using class inheritance, make sure that the relationship between the classes can fairly be described as is-a rather than has-a.

See Also